<template>
  <div id="productAnalysis">
    <product-analysis-header @changeGroupOrSplit="changeGroupOrSplit"
                             @timeChange="timeChange"
                             @radio2Change="radio2Change"
                             @radio1Change="radio1Change"></product-analysis-header>
    <div>
      <f-scroll :scrollStyle="wrapStyle"
                @scrollToEnd="scrollToEnd">
        <div class="content"
             :style="{'height': height + 'px'}"
             v-loading="loading"
             element-loading-text="Loading"
             element-loading-spinner="el-icon-loading"
             element-loading-background="rgba(0, 0, 0, 0.8)">
          <div class="wrap chart"
               v-if="mode === 'Charts' && contentShow">
            <div class="pie"
                 v-if="chartMode === 'pie'">
              <el-card v-for="(item,index) in options"
                       class="inline"
                       :key="'pie' + index">
                <div class="card-inner">
                  <div class="card-header">{{item.name}} (CN) - {{filterPrice(item.count *13)}} products</div>
                  <div class="card-chart"
                       @pieselectchanged="pieselectchanged"
                       v-for="(i,idx) in item.split"
                       :key="idx"
                       :id="'pie_chart_group'+ index + '_index' + idx "
                       :style="{'height': height - 120 + 'px','width': pieWidth + 'px'}">
                  </div>
                </div>
              </el-card>
            </div>
            <div class="bar"
                 v-else-if="chartMode === 'bar'">
              <el-card v-for="(item,index) in options"
                       :key="'bar' + index">
                <div class="card-chart"
                     :id="'bar_chart_group'+ index"
                     :style="{'height': height/2 - 110 + 'px','width': contentWidth + 'px'}">
                </div>
              </el-card>
            </div>
            <div class="boxplot"
                 v-else-if="chartMode === 'boxplot'">
              <el-card class="inline">
                <div class="card-inner">
                  <div class="card-chart"
                       id="box_chart_group"
                       :style="{'height': height - 120 + 'px','width': contentWidth - 100 + 'px'}">
                  </div>
                </div>
              </el-card>
            </div>
          </div>
          <div class="wrap table"
               v-if="mode === 'Table'  && contentShow">
            <div>
              <el-table :span-method="objectSpanMethod"
                        :data="options"
                        stripe
                        style="width: 99%"
                        :height="height -20">
                <el-table-column type="index"
                                 class-name="indexColumn"
                                 fixed
                                 width="200"
                                 :index="indexMethod">
                </el-table-column>
                <el-table-column v-for="item in options[0].split"
                                 :label="item.name"
                                 :key="item.id"
                                 align="left">
                  <el-table-column v-for="i in item.analysis"
                                   min-width="150"
                                   align="left"
                                   :key="i.id"
                                   :label="i.name">
                    <template slot-scope="scope">
                      {{getCount(scope.row, item.id, i[idType])}}
                    </template>
                  </el-table-column>

                </el-table-column>
              </el-table>
            </div>
          </div>
        </div>
      </f-scroll>
      <div v-show="pdShow"
           @mouseleave="mouseLeavePie"
           @keyup.esc="mouseLeavePie"
           tabindex="666"
           id="product-detail"
           :style="{left: x + 'px',top: y + 'px'}">
        <div class='tooltip-wrap'>
          <div class='header'> {{total}} products</div>
          <f-scroll :scrollStyle="wrapStyle"
                    :id="888"
                    class='product-list'
                    @scrollToEnd="productScrollToEnd">
            <div class="product"
                 v-for="item in products"
                 :key="item.product_id">
              <div class='left'><img :src="item.url"></div>
              <div class='right'>
                <div class='desc'>{{item.desc}}</div>
                <div class='price'>Sale:
                  <span class='num'> ${{item.price}}</span>
                </div>
              </div>
            </div>
          </f-scroll>
        </div>
      </div>
    </div>

  </div>
</template>

<script>
import productAnalysisHeader from "./productAnalysisHeader.c";
import { fillSpace } from "@/util/tool";
import {
  pieOption,
  pieSerie,
  barOption,
  barSerie,
  boxplotOption,
  boxSerie
} from "@/echart/echart-option";
import { prepareBoxplotData } from "@/echart/lux-data-tool";
import { mapGetters } from "vuex";
import { priceFilter } from "@/util/tool";
import { colors } from "@/util/config";

export default {
  data() {
    return {
      options: [],
      tableData: [],
      index: 0,
      wrapStyle: {
        height: ""
      },
      height: 0,
      pieWidth: 500,
      contentWidth: 0,
      countOrPercent: "Counts",
      chartOrTable: "",
      chartMode: "bar",
      contentShow: false,
      loading: false,
      mode: "Charts",
      params: {
        group: "retailer",
        split: "brands",
        time: 2017
      },
      pdShow: false,
      toProduct: false,
      x: 0,
      y: 0,
      total: "",
      lastPage: "",
      currentPage: 1,
      groupId: "",
      splitId: "",
      partId: "",
      products: []
    };
  },
  created() {},
  computed: {
    idType() {
      switch (this.chartShow) {
        case "series":
          return "id";
        case "material":
          return "material_id";
        case "color":
          return "color_id";
        case "type":
          return "type_id";
      }
    },
    ...mapGetters(["chartShow", "activeName", "imgUrl"])
  },
  mounted() {
    this.setContentWidth();
    this.setContentHeight();
    window.onresize = () => {
      this.setContentWidth();
      this.setContentHeight();
    };
  },
  methods: {
    init() {
      this.getData();
    },
    destory() {
      this.contentShow = false;
    },
    pieselectchanged() {},
    getCount(row, splitId, analysisId) {
      let split = row.split.find(item => item.id === splitId);
      let obj = split.analysis.find(item => item[this.idType] === analysisId);
      if (obj && obj.count) {
        return this.countOrPercent === "Counts"
          ? obj.count * 13
          : obj.percent + "%";
      } else {
        return "-";
      }
    },
    priceFilter(val) {
      return priceFilter(val);
    },
    indexMethod(index) {
      return (
        this.options[index].name +
        "\n" +
        priceFilter(this.options[index].count * 13) +
        "  products"
      );
    },
    getData() {
      this.setContentWidth();
      this.setContentHeight();
      this.contentShow = false;
      const params = Object.assign({}, this.params);
      params.filter = this.filter;
      params.analysis = this.chartShow;
      this.loading = true;
      switch (this.chartShow) {
        case "series":
        case "material":
        case "color":
        case "type":
          this.getPieData(params);
          break;
        case "newIn":
          this.getBarData(params);
          break;
        case "priceIndex":
          this.getBoxData(params);
          break;
      }
    },
    getPieData(params) {
      this.chartMode = "pie";
      this.$http.post("goods/chart", params).then(res => {
        this.options = res;
        this.$nextTick(() => {
          this.contentShow = true;
          if (this.mode === "Charts") {
            this.updatePieChart();
          } else {
            this.updateTable();
          }
        });
      });
    },
    getBarData(params) {
      this.chartMode = "bar";
      this.$http.post("goods/chart", params).then(res => {
        this.options = res;
        this.$nextTick(() => {
          this.contentShow = true;
          this.updateBarChart();
        });
      });
    },
    getBoxData(params) {
      this.chartMode = "boxplot";
      this.$http.post("goods/chart", params).then(res => {
        this.options = res;
        this.$nextTick(() => {
          this.contentShow = true;
          this.updateBoxChart();
        });
      });
    },
    objectSpanMethod({ row, column, rowIndex, columnIndex }) {},
    updateTable() {
      let allAnalysis = {};
      for (let i = 0; i < this.options.length; i++) {
        for (let j = 0; j < this.options[i].split.length; j++) {
          let data = this.options[i].split[j];
          let splitId = data.id;
          if (!allAnalysis[splitId]) {
            allAnalysis[splitId] = [];
          }
          let analysis = [];
          let other = {
            count: 0,
            name: "other",
            [this.idType]: 666666,
            percent: 0
          };
          for (let i of data.analysis) {
            if (i.percent > 5) {
              if (
                allAnalysis[splitId].every(
                  item => item[this.idType] !== i[this.idType]
                )
              ) {
                allAnalysis[splitId].push(i);
              }
              analysis.push(i);
            } else if (
              this.chartShow !== "color" &&
              this.chartShow !== "material"
            ) {
              other.count += i.count;
              other.percent += Number(i.percent);
              other.percent = Math.round(other.percent * 100) / 100;
            }
          }
          if (
            this.chartShow !== "color" &&
            this.chartShow !== "material" &&
            other.count
          ) {
            analysis.push(other);
          }
          data.analysis = analysis;
        }
      }
      this.fillZero(allAnalysis);
      this.loading = false;
    },
    fillZero(allAnalysis) {
      for (let i = 0; i < this.options.length; i++) {
        for (let j = 0; j < this.options[i].split.length; j++) {
          let data = this.options[i].split[j];
          let splitId = data.id;
          for (let o of allAnalysis[splitId]) {
            let fei = data.analysis.find(
              item => item[this.idType] === o[this.idType]
            );
            if (!fei) {
              data.analysis.push({
                count: 0,
                name: o.name,
                [this.idType]: o[this.idType],
                percent: 0
              });
              data.analysis.sort((a, b) => {
                return a[this.idType] - b[this.idType];
              });
            }
          }
        }
      }
    },
    updatePieChart() {
      let pd = document.getElementById("product-detail");
      this.$nextTick(() => {
        for (let i = 0; i < this.options.length; i++) {
          for (let j = 0; j < this.options[i].split.length; j++) {
            let dom = document.getElementById(
              "pie_chart_group" + i + "_index" + j
            );
            let chart = this.$echarts.init(dom);
            let data = this.options[i].split[j];
            let analysis = [];
            let other = {
              count: 0,
              name: "other",
              [this.idType]: [],
              percent: 0
            };
            for (let i of data.analysis) {
              if (i.percent > 5) {
                analysis.push(i);
              } else if (
                this.chartShow !== "color" &&
                this.chartShow !== "material"
              ) {
                other.count += i.count;
                other.percent += Number(i.percent);
                other.percent = Math.round(other.percent * 100) / 100;
                other[this.idType].push(i[this.idType]);
              }
            }
            if (
              this.chartShow !== "color" &&
              this.chartShow !== "material" &&
              other.count
            ) {
              analysis.push(other);
            }
            let pie = new pieOption();
            pie.groupId = this.options[i].id;
            pie.splitId = data.id;
            pie.chartStyle = this.chartShow;
            pie.title.text = data.name;
            pie.title.subtext =
              " " + priceFilter(data.count * 13) + " Products"; //改变subtext
            let color;
            let serie;
            chart.on("click", params => {
              this.pdShow = true;
              let event = params.event.event;
              event.stopPropagation();
              this.x = event.clientX - 280;
              this.y = event.clientY - 90;
              let partId = params.value.id;
              this.groupId = pie.groupId;
              this.splitId = pie.splitId;
              this.partId = partId;
              let searchParams = {
                filter: this.filter,
                group: this.params.group,
                split: this.params.split,
                chartStyle: this.chartShow,
                groupId: this.groupId,
                splitId: this.splitId,
                partId: this.partId
              };
              this.$http.post("goods/pi", searchParams).then(res => {
                let data = res.data.map(item => {
                  return {
                    url: this.imgUrl + item.product_id + "/1.jpg",
                    product_id: item.product_id,
                    desc: item.desc,
                    price: item.price
                  };
                });
                let dom = document.querySelector("#product-detail");
                this.$nextTick(() => {
                  dom.focus();
                });
                this.total = params.data.value * 13;
                this.products = data;
                this.currentPage = res.current_page;
                this.lastPage = res.last_page;
              });
            });

            if (this.chartShow === "color") {
              let colorArr = colors.map(item => item.value);
              pie.color = colorArr;
              analysis.forEach(item => {
                serie = new pieSerie();
                pie.series.push(serie);
              });
            } else {
              analysis.forEach(item => {
                serie = new pieSerie();
                pie.series.push(serie);
              });
            }

            pie.legend.data = analysis.map(item => {
              // legend补空格
              const name =
                fillSpace(item.name, 15) +
                (this.countOrPercent === "Counts"
                  ? priceFilter(item.count * 13)
                  : item.percent + "%");
              return {
                name: name
              };
            });
            pie.dataset.source = analysis.map(item => {
              //  data补空格
              const name =
                fillSpace(item.name, 15) +
                (this.countOrPercent === "Counts"
                  ? priceFilter(item.count * 13)
                  : item.percent + "%");
              return {
                name: name,
                value: item.count,
                id: item[this.idType]
              };
            });
            chart.setOption(pie);
          }
        }
        this.loading = false;
      });
    },
    updateBarChart() {
      this.$nextTick(() => {
        for (let i = 0; i < this.options.length; i++) {
          let data = this.options[i];
          let chart = this.$echarts.init(
            document.getElementById("bar_chart_group" + i)
          );
          let bar = new barOption();
          let dimensions = data.data[0];
          let len = dimensions.length;
          bar.legend.data = dimensions.slice(1);
          bar.title.text = "New in - " + data.name;
          for (let j = 0; j < len - 1; j++) {
            let serie = new barSerie();
            bar.series.push(serie);
          }
          bar.dataset.source = data.data;
          chart.setOption(bar);
        }
        this.loading = false;
      });
    },
    updateBoxChart() {
      this.$nextTick(() => {
        const data = [];
        const bgColorArr = [
          "#9bcdfb",
          "#febfc0",
          "#99eae2",
          "#d5f3b0",
          "#c5c6f4",
          "#ffe8bc",
          "#f7c9fa",
          "#ffcebd",
          "#b3e6fb",
          "#feb7d7"
        ];
        let index = 0;
        const bgLen = bgColorArr.length;
        const chart = this.$echarts.init(
          document.getElementById("box_chart_group")
        );
        const oData = this.options.data;
        for (let i = 0; i < oData.length; i++) {
          const origin = prepareBoxplotData(oData[i].origin);
          data.push(origin);
        }
        const len = data.length;
        const groupData = this.options.groupData;
        const boxplot = new boxplotOption(data, groupData);
        let legendData = oData.map(item => item.name);
        for (let i = 0; i < len; i++) {
          let color = bgColorArr[index];
          if (index <= bgLen) {
            index++;
          } else {
            index = 0;
          }
          boxplot.series.push(
            new boxSerie(i, data[i].boxData, legendData, color)
          );
        }
        boxplot.legend.data = legendData;
        chart.setOption(boxplot);
        this.loading = false;
      });
    },
    scrollToEnd() {},
    productScrollToEnd() {
      if (this.currentPage < this.lastPage) {
        let searchParams = {
          filter: this.filter,
          group: this.params.group,
          split: this.params.split,
          chartStyle: this.chartShow,
          groupId: this.groupId,
          splitId: this.splitId,
          partId: this.partId
        };
        this.$http
          .post("goods/pi?page=" + (this.currentPage + 1), searchParams)
          .then(res => {
            let data = res.data.map(item => {
              return {
                url: this.imgUrl + item.product_id + "/1.jpg",
                product_id: item.product_id,
                desc: item.desc,
                price: item.price
              };
            });
            this.products = this.products.concat(data);
            this.currentPage = res.current_page;
            this.lastPage = res.last_page;
          });
      }
    },
    mouseLeavePie() {
      this.pdShow = false;
      this.toProduct = false;
      this.products = [];
    },
    mouseOverPd() {
      this.toProduct = true;
    },
    filterPrice(num) {
      return priceFilter(num);
    },
    radio1Change(val) {
      this.mouseLeavePie();
      this.mode = val;
      this.getData();
    },
    radio2Change(val) {
      this.mouseLeavePie();
      this.countOrPercent = val;
      this.getData();
    },
    timeChange(val) {
      this.params.time = val;
      this.getData();
    },
    changeGroupOrSplit(val) {
      this.params.split = val.split;
      this.params.group = val.group;
      this.getData();
    },
    setContentHeight() {
      this.$nextTick(() => {
        let dom = document.querySelector(".content");
        let len = document.body.offsetHeight;
        this.height = len - 176;
      });
    },
    setContentWidth() {
      this.$nextTick(() => {
        let dom = document.querySelector(".content");
        let len = document.body.clientWidth - 350;
        this.contentWidth = len;
      });
    }
  },
  components: {
    productAnalysisHeader
  },
  watch: {
    chartShow(newVal, oldVal) {
      this.mouseLeavePie();
      this.getData();
    },
    filter(curVal, oldVal) {
      if (this.activeName === "second") {
        this.mouseLeavePie();
        this.getData();
      }
    }
  }
};
</script>

<style lang="scss">
@import "../../../assets/styles/color.scss";
@import "../../../assets/styles/mixins.scss";

#productAnalysis {
  .table {
    white-space: nowrap;
    padding: 10px 5px;
    background-color: white;
    margin-left: 10px;
  }
  .el-table thead.is-group th {
    background-color: #f3f5f9;
  }
  .el-table__row--striped td {
    background-color: #f3f5f9;
  }
  tr:hover td {
  }
  .el-table table {
    tr {
      border: 1px solid #e5e9eb;
    }
  }
  .cell {
    text-align: center;
  }

  .indexColumn {
    .cell {
      white-space: pre;
    }
  }
  .el-table {
    margin-left: 10px;
  }
  .el-table__row {
    td {
      width: 300px;
    }
  }
  .content {
    overflow-y: auto;
    overflow-x: auto;
    white-space: nowrap;
    .el-card {
      margin-bottom: 30px;
      margin-left: 10px;
      margin-right: 20px;
      margin-bottom: 20px;
    }
    .el-card.inline {
      display: inline-block;

      .el-card__body > .card-inner {
        display: inline-block;
        .card-header {
          text-align: center;
          text-indent: 10px;
          font-size: 25px;
        }
        .card-chart {
          display: inline-block;
        }
      }
    }
  }
  .tooltip-wrap {
    border: 1px solid #ccc;
    color: black;
    text-align: left;
    max-height: 270px;
    outline: none;
    .header {
      font-size: 14px;
      background-color: #f7f7f7;
      height: 30px;
      line-height: 30px;
      text-indent: 10px;
      padding-right: 10px;
    }
    .product-list {
      &::-webkit-scrollbar {
        width: 5px;
      }
      max-height: 240px;
      overflow: auto;
      background-color: #fff;
      .product {
        height: 120px;
        .left {
          margin-left: 10px;
          margin-right: 10px;
          float: left;
          img {
            width: 100px;
            height: 100px;
            margin-top: 10px;
          }
        }
        .right {
          margin-right: 10px;
          max-width: 150px;
          .desc {
            line-height: 25px;
            font-size: 16px;
            margin-top: 35px;
            overflow: hidden;
            text-overflow: ellipsis;
            white-space: nowrap;
          }
          .price {
            line-height: 25px;
            font-size: 16px;
            .num {
              color: $base;
            }
          }
          overflow: hidden;
        }
      }
    }
  }
  #product-detail {
    outline: none;
    position: absolute;
    z-index: 10000;
  }
}
</style>
